<template>
  <div class="swiper">
    <div class="swiper-slide">
      <!-- 是否卡片轮播 -->
      <div
        class="swiper-slide-wrap"
        ref="swiper"
        @mouseenter="mouseenter"
        @mouseleave="mouseleave"
      >
        <!-- 轮播方向 -->
        <div
          class="swiper-slide-wrap-list"
          :class="{
            'swiper-slide-wrap-list-flex': isVertical,
            'swiper-slide-wrap-transition': noLast && !isFade,
          }"
          ref="content"
          :style="{ transform }"
        >
          <slot />
        </div>
      </div>
      <!-- 锚点 test -->
      <!-- 是否展示锚点 -->
      <div
        v-if="dots"
        class="swiper-slide-dots"
        :class="`swiper-slide-dots-${vertical}`"
      >
        <div
          class="swiper-slide-dots-item"
          :class="`swiper-slide-dots-${anchorPointStyle} swiper-slide-dots-${vertical}-${anchorPointStyle} ${
            index === activeIndex ? 'swiper-slide-dots-item-active' : ''
          }`"
          v-for="(dot, index) in childList"
          :key="index"
          @click="switchSwiple(index)"
        ></div>
      </div>
      <!-- 展示页数 111-->
      <div
        v-if="isShowPagination"
        class="swiper-slide-pagination"
        :class="{
          'swiper-slide-pagination-card': cardSwiper,
          'swiper-slide-pagination-white': isAddCard,
        }"
      >
              <span>{{ childList.length ? activeIndex + 1 : 0 }}</span>

        <span>/</span>
                <span>{{ childList.length }}</span>

      </div>
    </div>
  </div>
</template>
<script>
export default {
  name: 'swiper',
  props: {
    // 轮播速度
    speed: {
      type: Number,
      default: 1000,
    },
    /* 轮播方向
     * vertical 垂直方向
     * horizontal 水平方向
     */
    vertical: {
      type: String,
      default: 'right',
    },
    // 卡片轮播
    cardSwiper: {
      type: Boolean,
      default: false,
    },
    // 添加白底
    isAddCard: {
      type: Boolean,
      default: false,
    },
    // 自动播放
    autoplay: {
      type: Boolean,
      default: true,
    },
    // 是否展示页数
    isShowPagination: {
      type: Boolean,
      default: true,
    },
    // 是否展示锚点
    dots: {
      type: Boolean,
      default: true,
    },
    // 锚点样式
    // circle  line
    anchorPointStyle: {
      type: String,
      default: 'circle',
    },
    // 动效类型
    effect: {
      type: String,
      default: 'fade',
    },
    // 数据
    dataSourceList: {
      type: Array,
      default: () => [],
    },
  },
  data() {
    return {
      // 所有子集
      childList: [],
      // 当前循环到第几页数
      currentPage: 1,
      // 当前锚点到下标
      activeIndex: 0,
      // 是否开启滑动
      noLast: false,
      // 宽度
      swipleWidth: 0,
      // 高度
      swipleHeight: 0,
      // 定时器
      timer: null,
      // 卡片的参数
      swipleItemParams: {
        // 拿到的宽度需要减去的值
        result: 44,
        // 是需要看到其余卡片的宽度
        margin: 17,
        // 中间距离
        center: 8,
      },
    }
  },
  computed: {
    // 是否垂直渲染
    isVertical() {
      return this.vertical === 'bottom'
    },
    /* 如果是水平移动
     * 平移x轴
     * 否则y轴
     * 如果是卡片轮播的话
     * 每个卡片的宽度是
     * this.currentPage * (this.swipleWidth - 44) 是每个卡片的宽度
     * 17 是需要看到其余卡片的宽度
     * 8 为两个轮播中间距离
     */
    transform() {
      if (this.isVertical) {
        return this.cardSwiper
          ? `translateX(-${
              this.currentPage *
                (this.swipleWidth - this.swipleItemParams.result) -
              this.swipleItemParams.margin +
              this.swipleItemParams.center * this.currentPage
            }px)`
          : `translateX(-${this.currentPage * this.swipleWidth}px)`
      }
      {
        return `translateY(-${this.currentPage * this.swipleHeight}px)`
      }
    },
    // 多两张图片
    swipleList() {
      if (this.childList.length > 1) {
        return [
          this.childList[this.childList.length - 1],
          ...this.childList,
          this.childList[0],
        ]
      }
    },
    // 是否是渐变
    isFade() {
      return this.effect === 'fade'
    },
  },
  created() {
    this.$nextTick(() => {
      this.switchCard()
    })
  },
  watch: {
    dataSourceList(value) {
      setTimeout(() => {
        this.initChildren()
        // 自动播放
        this.mouseleave()
      })
    },
  },
  mounted() {
    // 默认宽度和高度
    // 平移一个点距离
    this.swipleWidth = this.$refs.swiper.offsetWidth
    this.swipleHeight = this.$refs.swiper.offsetHeight

    setTimeout(() => {
      this.initChildren()

      // 自动播放ref
      this.mouseleave()
    }, 2000)
  },
  methods: {
    switchCard() {
      const children = this.$refs['content'].children

      // 如果开启卡片轮播
      for (let i = 0; i < children.length; i++) {
        if (this.cardSwiper) children[i].addCard = true
        if (this.isAddCard) children[i].addWhite = true
      }
      // children.forEach((item) => {
      //   console.log(33, item)
      //   if (this.cardSwiper) item.addCard = true
      //   if (this.isAddCard) item.addWhite = true
      // })
    },
    /* 点击切换轮博 */
    switchSwiple(index) {
      this.activeIndex = index
      this.currentPage = index + 1
    },
    /* 鼠标进入清除定时器 */
    mouseenter() {
      clearInterval(this.timer)
      this.timer = null
    },
    /* 鼠标离开重新开始 */
    mouseleave() {
      this.mouseenter()

      // 自动播放
      if (this.autoplay) {
        this.startPlay()
      }
    },
    /* 获取子集 */
    initChildren() {
      const chOld = this.$refs['content'].children
      const chNew = []
      for (let i = 0; i < chOld.length; i++) {
        chNew.push(chOld[i])
      }

      this.childList = chNew
      let children = this.$refs['content'].children
      // 添加两个元素
      if (this.childList.length > 1) {
        this.childList
          .filter((_item, index) => children[index].initSwipleLast)
          .forEach((_item, index) => {
            this.$el.removeChild(children[index])
          })
        // 默认显示第二个
        const preChild = children[children.length - 1].cloneNode(true)
        preChild.initSwipleLast = true
        this.$refs['content'].prepend(preChild)
        const appChild = children[1].cloneNode(true)
        appChild.initSwipleLast = true
        this.$refs['content'].appendChild(appChild)
      } else {
        this.currentPage = 0
      }
      setTimeout(() => {
        //如果是左右滑动的话开启动画
        if (!this.isFade) {
          this.noLast = true
        }
      })
    },
    /* 开启定时器 */
    startPlay() {
      this.timer = setInterval(() => {
        this.next()
      }, this.speed)
    },
    /* 切换下一张 */
    next() {
      // 如果只有一个子元素 不需要移动
      if (this.childList.length < 2) return
      this.currentPage++
      // 如果移到最后一张 切换回第一张
      this.activeIndex =
        this.childList.length - 1 === this.activeIndex
          ? 0
          : this.activeIndex + 1
      // 如果到最后一个
      if (this.currentPage === this.swipleList.length - 1) {
        // 动效类型是否是左右滑动， 如果是的话添加定时器
        if (!this.isFade) {
          // 已经到最后一个
          // 设置和动画时间一致 清掉动画 平移到第一个
          setTimeout(() => {
            this.noLast = false
            this.currentPage = 1
          }, 500)
        } else {
          this.noLast = false
          this.currentPage = 1
        }
      }
      this.noLast = true
    },
  },
}
</script>
<style scoped lang="less">
.swiper {
  position: relative;
  overflow: hidden;
  height: 100%;
  &-slide {
    width: 100%;
    height: 100%;
    position: relative;
    &-wrap {
      height: 100%;
      // 白底

      &-transition {
        transition: all 0.5s;
      }
      // 列表
      &-list {
        height: 100%;
        div {
          height: 100%;
        }
        &-flex {
          display: flex;
        }
      }
    }
    // 锚点
    &-dots {
      position: absolute;

      &-bottom {
        display: flex;
        left: 50%;
        bottom: 0px;
        transform: translateX(-50%);
        &-line {
          width: 20px;
          height: 4px;
        }
      }
      &-right {
        right: 8px;
        top: 50%;
        transform: translateY(-50%);
        &-line {
          width: 4px;
          height: 20px;
        }
      }
      &-item {
        transition: all 0.5s;
        background: rgba(5, 6, 26, 0.06);
        cursor: pointer;
        &-active {
          background-color: #333cff;
          opacity: 1;
        }
      }
      &-circle {
        width: 6px;
        height: 6px;
        border-radius: 100%;
        margin-right: 8px;
        margin-bottom: 8px;
      }
      &-line {
        margin-right: 4px;
        margin-bottom: 8px;
      }
    }
    // 分页
    &-pagination {
      position: absolute;
      z-index: 99;
      background: rgba(5, 6, 26, 0.26);
      padding: 1px 8px;
      border-radius: 13px;
      bottom: 4px;
      right: 5px;
      &-card {
        right: 26px;
      }
      &-white {
        bottom: 22px;
        right: 16px;
      }
    }
  }
}
</style>
